from flask import Flask, render_template, request, jsonify, redirect, url_for
import json
import os
import sys
from datetime import datetime

# PyInstaller环境下的资源路径处理
def get_resource_path(relative_path):
    """获取资源文件的绝对路径，兼容PyInstaller打包环境（one-dir模式）"""
    try:
        # PyInstaller创建临时文件夹，并将路径存储在_MEIPASS中
        # 对于one-dir模式，我们直接使用当前目录
        if hasattr(sys, '_MEIPASS'):
            # 检查是否是one-file模式
            if not os.path.isdir(sys._MEIPASS + '\\templates'):
                # 如果是one-file模式，使用_MEIPASS
                base_path = sys._MEIPASS
            else:
                # 如果是one-dir模式，使用可执行文件所在目录
                base_path = os.path.dirname(os.path.abspath(sys.executable))
        else:
            # 开发环境下，使用当前目录
            base_path = os.path.abspath(".")
    except Exception:
        base_path = os.path.abspath(".")
    return os.path.join(base_path, relative_path)

# 配置Flask应用，指定模板和静态文件路径
app = Flask(__name__, 
            template_folder=get_resource_path('templates'),
            static_folder=get_resource_path('static'))

# 配置文件路径 - 外部可修改的配置文件
CONFIG_FILE = get_resource_path('config/sites_config.json')

# 默认配置
DEFAULT_CONFIG = {
    "sites": [
        {
            "name": "镇江",
            "host": "localhost",
            "port": "5000",
            "enabled": True
        },
        {
            "name": "雍熙",
            "host": "localhost",
            "port": "5001",
            "enabled": True
        },
        {
            "name": "同方",
            "host": "localhost",
            "port": "5002",
            "enabled": True
        }
    ]
}

def load_config():
    """加载配置文件"""
    if not os.path.exists(CONFIG_FILE):
        # 如果配置文件不存在，创建默认配置
        os.makedirs(os.path.dirname(CONFIG_FILE), exist_ok=True)
        save_config(DEFAULT_CONFIG)
        return DEFAULT_CONFIG
    
    try:
        with open(CONFIG_FILE, 'r', encoding='utf-8') as f:
            return json.load(f)
    except Exception as e:
        print(f"加载配置文件失败: {e}")
        return DEFAULT_CONFIG

def save_config(config):
    """保存配置文件"""
    try:
        os.makedirs(os.path.dirname(CONFIG_FILE), exist_ok=True)
        with open(CONFIG_FILE, 'w', encoding='utf-8') as f:
            json.dump(config, f, ensure_ascii=False, indent=2)
        return True
    except Exception as e:
        print(f"保存配置文件失败: {e}")
        return False

@app.route('/')
def index():
    """导航首页"""
    config = load_config()
    return render_template('index.html', sites=config['sites'])

@app.route('/config')
def config_page():
    """配置页面"""
    config = load_config()
    return render_template('config.html', sites=config['sites'])

@app.route('/api/config', methods=['GET', 'POST'])
def api_config():
    """配置API"""
    if request.method == 'GET':
        config = load_config()
        return jsonify(config)
    
    elif request.method == 'POST':
        try:
            new_config = request.get_json()
            if save_config(new_config):
                return jsonify({"success": True, "message": "配置保存成功"})
            else:
                return jsonify({"success": False, "message": "配置保存失败"}), 500
        except Exception as e:
            return jsonify({"success": False, "message": f"配置保存失败: {str(e)}"}), 500

@app.route('/api/test_connection', methods=['POST'])
def test_connection():
    """测试连接"""
    try:
        import socket
        from urllib.parse import urlparse
        import requests
        
        data = request.get_json()
        host = data.get('host')
        port = data.get('port')
        site_name = data.get('name', '未知站点')  # 获取站点名称，默认为'未知站点'
        
        if not host or not port:
            return jsonify({"success": False, "message": "缺少主机地址或端口号"}), 400
        
        # 尝试转换端口为整数
        try:
            port_int = int(port)
        except ValueError:
            return jsonify({"success": False, "message": "端口号格式错误"}), 400
        
        # 1. 首先测试TCP连接
        try:
            sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            sock.settimeout(5)  # 5秒超时
            result = sock.connect_ex((host, port_int))
            sock.close()
            
            if result != 0:
                return jsonify({"success": False, "message": f"{site_name}({host}:{port}) TCP连接失败"}), 500
        except Exception as e:
            return jsonify({"success": False, "message": f"{site_name}({host}:{port}) 网络连接异常: {str(e)}"}), 500
        
        # 2. 如果TCP连接成功，尝试HTTP请求
        try:
            url = f"http://{host}:{port}/"
            response = requests.get(url, timeout=10)
            
            if response.status_code == 200:
                return jsonify({"success": True, "message": f"{site_name}({host}:{port}) 连接测试成功，服务正常运行"})
            else:
                return jsonify({"success": False, "message": f"{site_name}({host}:{port}) HTTP响应异常，状态码: {response.status_code}"}), 500
                
        except requests.exceptions.Timeout:
            return jsonify({"success": False, "message": f"{site_name}({host}:{port}) HTTP请求超时"}), 500
        except requests.exceptions.ConnectionError:
            return jsonify({"success": False, "message": f"{site_name}({host}:{port}) HTTP连接被拒绝"}), 500
        except Exception as e:
            return jsonify({"success": False, "message": f"{site_name}({host}:{port}) HTTP请求失败: {str(e)}"}), 500
            
    except Exception as e:
        return jsonify({"success": False, "message": f"连接测试失败: {str(e)}"}), 500

if __name__ == '__main__':
    app.run(debug=True, host='0.0.0.0', port=5000)